package com.gzhryc.shared_device.oem.h5.agent.controllers.api.v1.market;

import java.util.ArrayList;
import java.util.Date;
import java.util.List;

import javax.servlet.http.HttpServletRequest;

import com.gzhryc.common.NumberTools;
import com.gzhryc.common.StringTools;
import com.gzhryc.common.exceptions.LogicException;
import com.gzhryc.common.json.JsonTools;
import com.gzhryc.common.logging.Logger;
import com.gzhryc.net_marketing.cloud.business.dao.db.UserPayGoodsOrder;
import com.gzhryc.net_marketing.cloud.business.services.UserPayGoodsOrderService;
import com.gzhryc.net_marketing.cloud.goods.dao.db.Goods;
import com.gzhryc.net_marketing.cloud.goods.dao.db.GoodsSpace;
import com.gzhryc.net_marketing.cloud.goods.dao.enums.GoodsEnum;
import com.gzhryc.net_marketing.cloud.goods.services.GoodsService;
import com.gzhryc.net_marketing.cloud.goods.services.GoodsSpaceService;
import com.gzhryc.net_marketing.cloud.logistics.LogisticsCostUtils;
import com.gzhryc.pay.adaptation.weixin.PayJSConfig;
import com.gzhryc.pay.adaptation.weixin.WXPayNormalPayService;
import com.gzhryc.pay.adaptation.weixin.msg.normal.WXPayNormalPayResponse;
import com.gzhryc.servlet.WebUtils;
import com.gzhryc.servlet.annotation.Route;
import com.gzhryc.shared_device.base.ILogisticsCostConfig;
import com.gzhryc.shared_device.common.payment.dao.db.WXPayOrder;
import com.gzhryc.shared_device.common.payment.services.WXPayOrderService;
import com.gzhryc.shared_device.oem.code.PayServiceFactory;
import com.gzhryc.shared_device.oem.code.business.EBusinessType;
import com.gzhryc.shared_device.oem.code.user.dao.db.UserAddress;
import com.gzhryc.shared_device.oem.code.user.services.UserAddressService;
import com.gzhryc.shared_device.oem.h5.agent.ClientAPICodeConstants;
import com.gzhryc.shared_device.oem.h5.agent.LoginUser;
import com.gzhryc.shared_device.oem.h5.agent.WebConstants;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.market.LogisticsCostListRequest;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.market.LogisticsCostListResponse;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.market.PayGoodsRequest;
import com.gzhryc.shared_device.oem.h5.agent.dto.api.v1.market.PayGoodsResponse;

public class GoodsPayController {

    static Logger log = Logger.getLogger(GoodsPayController.class);

    @Route(value = {"/agent_market/api/v1/logistics/cost/list.do"})
    public LogisticsCostListResponse findLogisticsCostList(HttpServletRequest request) {
        LogisticsCostListResponse apiResp = new LogisticsCostListResponse(ClientAPICodeConstants.NULL_DATA, "暂无数据");
        LogisticsCostListRequest apiReq = WebUtils.getJsonRequest(request, LogisticsCostListRequest.class);
        LoginUser loginUser = WebUtils.getAttribute(request, WebConstants.ATTR_LOGIN_USER, LoginUser.class);
        if (apiReq != null && loginUser != null && apiReq.getBody().getAddressId() != null) {
            if (loginUser.getId() == null) {
                apiResp.setMsg("请注册用户后再购买");
                return apiResp;
            }
            try {
                UserAddress userAddress = UserAddressService.self().getByIdAndUserId(apiReq.getBody().getAddressId(), loginUser.getId());
                if (userAddress == null) {
                    apiResp.setMsg("未找到用户收货地址");
                    return apiResp;
                }

                List<ILogisticsCostConfig> costConfigList = LogisticsCostUtils.findCostConfig(null,userAddress.getProvince());
                if(costConfigList != null && costConfigList.size() > 0){
                    apiResp.setCode(ClientAPICodeConstants.SUCCESS,null);
                    apiResp.getBody().setItems(new ArrayList<>());

                    for(ILogisticsCostConfig costConfig : costConfigList){
                        LogisticsCostListResponse.LogisticsItem item = new LogisticsCostListResponse.LogisticsItem();
                        item.setCompanyId(costConfig.getCompanyId());
                        item.setName(costConfig.getCompanyName());
                        item.setMoney(NumberTools.getMoneyStr(costConfig.getMoney()));
                        if(costConfig.getFreeMinMoney() != null && costConfig.getFreeMinMoney() > 0){
                            item.setNote("消费" + NumberTools.getMoneyStr(costConfig.getFreeMinMoney()) + "元免邮费");
                        }
                        apiResp.getBody().getItems().add(item);
                    }
                }
            } catch (Exception e) {
                log.error(e.getMessage(), e);
            }
        }
        return apiResp;
    }

    @Route(value = {"/agent_market/api/v1/goods/pay.do"})
    public PayGoodsResponse payGoods(HttpServletRequest request) {
        PayGoodsResponse apiResp = new PayGoodsResponse(ClientAPICodeConstants.EXECUTE_ERROR, "购买失败，请稍后再试！");
        PayGoodsRequest apiReq = WebUtils.getJsonRequest(request, PayGoodsRequest.class);
        if (apiReq != null && apiReq.getBody().getGoodsId() != null && apiReq.getBody().getGoodsNum() != null) {
            LoginUser loginUser = WebUtils.getAttribute(request, WebConstants.ATTR_LOGIN_USER, LoginUser.class);
            if (loginUser.getId() == null) {
                apiResp.setMsg("请注册用户后再购买");
                return apiResp;
            }
            //全局判断
            if (apiReq.getBody().getPayMoney() > 0) {
                if (StringTools.isBlank(apiReq.getBody().getAppId()) || apiReq.getBody().getPayType() == null) {
                    apiResp.setMsg("未知的支付应用");
                    return apiResp;
                }
            }
            Goods goods = GoodsService.self().getById(apiReq.getBody().getGoodsId());
            if (goods == null || !GoodsEnum.State.PutOnTheShelf.index().equals(goods.getState())) {
                apiResp.setMsg("未找到商品或商品已下架");
                return apiResp;
            }
            GoodsSpace goodsSpace = null;
            if (apiReq.getBody().getSpecificationId() != null) {
                goodsSpace = GoodsSpaceService.self().getByKeys(apiReq.getBody().getGoodsId(), apiReq.getBody().getSpecificationId());
                if (goodsSpace == null) {
                    apiResp.setMsg("未找到商品的指定规格");
                    return apiResp;
                }
            }

            UserAddress userAddress = UserAddressService.self().getByIdAndUserId(apiReq.getBody().getAddressId(), loginUser.getId());
            if (userAddress == null) {
                apiResp.setMsg("未找到用户收货地址");
                return apiResp;
            }

            ILogisticsCostConfig logisticsCostConfig = null;
            try {
                logisticsCostConfig = LogisticsCostUtils.getUsableConfig(goods.getSupplierId(),apiReq.getBody().getLogisticsCompanyId()
                		, userAddress.getProvince());
            } catch (LogicException e) {
                apiResp.setMsg(e.getMessage());
                return apiResp;
            }

            if (logisticsCostConfig == null) {
                apiResp.setMsg("未找到物流服务");
                return apiResp;
            }

            try {
                UserPayGoodsOrder goodsPayOrder = UserPayGoodsOrderService.self().buildPayGoodsOrder(goods, goodsSpace, apiReq.getBody().getGoodsNum());
                goodsPayOrder.setUserId(loginUser.getId());
                goodsPayOrder.setUserName(loginUser.getName());
                goodsPayOrder.setUserPhone(loginUser.getPhone());

                goodsPayOrder.setMailAddressId(userAddress.getId());
                goodsPayOrder.setReceiveName(userAddress.getReceiveName());
                goodsPayOrder.setReceivePhone(userAddress.getReceivePhone());
                goodsPayOrder.setReceiveProvince(userAddress.getProvince());
                String receiveAddress = userAddress.getProvince() + userAddress.getCity()
                        + userAddress.getCityArea() + userAddress.getAddress();
                goodsPayOrder.setReceiveAddress(receiveAddress);

                goodsPayOrder.setLogisticsCompanyId(logisticsCostConfig.getCompanyId());
                goodsPayOrder.setLogisticsCompany(logisticsCostConfig.getCompanyName());
                if (goodsPayOrder.getMoney() >= logisticsCostConfig.getFreeMinMoney()) {
                    goodsPayOrder.setLogisticsMoney(0);
                } else {
                    goodsPayOrder.setLogisticsMoney(logisticsCostConfig.getMoney());
                }

                goodsPayOrder.setMoney(goodsPayOrder.getMoney() + goodsPayOrder.getLogisticsMoney());
                goodsPayOrder.setPayMoney(goodsPayOrder.getMoney());
                goodsPayOrder.setPayType(apiReq.getBody().getPayType());

                WXPayOrder payOrder = null;
                if (payOrder != null) {
                    WXPayNormalPayService normalPayService = PayServiceFactory.self().getWXPayNormalPayService(apiReq.getBody().getAppId(), EBusinessType.MARKET.index());
                    WXPayNormalPayResponse externalResult = normalPayService.applyPayOrder(payOrder);
                    if (externalResult != null) {
                        String prepayId = externalResult.getPrepay_id();
                        if (prepayId != null) {
                            WXPayOrderService.self(payOrder.getCreateDate()).updateExternalContent(payOrder.getTradeNo(), JsonTools.toJson(externalResult), new Date());
                            PayJSConfig payJsConfig = normalPayService.buildJSConfig(prepayId);
                            log.info("微信支付返回：" + payJsConfig);
                            apiResp.setCode(ClientAPICodeConstants.SUCCESS, null);
                            apiResp.getBody().setTradeNo(goodsPayOrder.getTradeNo());
                            apiResp.getBody().setPayType(apiReq.getBody().getPayType());
                            apiResp.getBody().setPayInfo(payJsConfig);
                        } else {
                            throw new LogicException("微信支付返回prepay_id参数为空");
                        }
                    }
                }
            } catch (LogicException e) {
                apiResp.setMsg(e.getMessage());
            }
        } else {
            apiResp.setMsg("商品参数错误");
        }
        return apiResp;
    }
}
